<template>
    <div>
        <Spin :spinning="loading" :delay="100">
            <div class="grouping" :style="{width: `${width}px`}">
                <div class="header">
                    <div class="flex header-title">
                        <div>{{ title }}</div>
                        <Button
                            v-show="enableAdd"
                            type="primary"
                            @click="handleOpen"
                            :size="'small'"
                            :icon="h(PlusOutlined)"
                            ghost
                        />
                    </div>
                    <slot name="search" />
                </div>
                <div class="list" v-if="list">
                    <div class="item flex" v-for="item in list" :key="item[config.key]">
                        <div class="flex item-left">
                            <AppstoreOutlined class="icon" :style="{fontSize: '16px'}" />
                            <div class="title">{{ item[config.title] }}</div>
                            <div class="num" v-if="item[config.num]">({{ item?.num }})</div>
                        </div>
                        <a-dropdown placement="bottom">
                            <EllipsisOutlined :style="{fontSize: '16px'}" />
                            <template #overlay>
                                <a-menu>
                                    <a-menu-item @click="handleEdit(item)">编辑</a-menu-item>
                                    <a-menu-item @click="handleDelete(item)">删除 </a-menu-item>
                                </a-menu>
                            </template>
                        </a-dropdown>
                    </div>
                </div>
            </div>
        </Spin>

        <Modal
            v-model:open="open"
            :bodyStyle="{padding: '24px 0'}"
            :title="`${textType[type]}${title}`"
            @ok="handleOk"
            ok-text="确认"
            cancel-text="取消"
        >
            <Form :form="form">
                <SchemaField :schema="schema" />
            </Form>
        </Modal>
    </div>
</template>

<script setup lang="ts">
import _ from "lodash";
import {h, reactive, ref, toRaw} from "vue";
import {createForm} from "@formily/core";
import {Modal, Spin, Button} from "ant-design-vue";
import {createSchemaField} from "@formily/vue";
import {FormItem, Form, Input} from "@formily/antdv";
import {PlusOutlined, EllipsisOutlined, AppstoreOutlined} from "@ant-design/icons-vue";

interface Props {
    /** 数据 */
    data?: any[];
    /** 宽度 */
    width?: number;
    /** 是否可以添加 */
    enableAdd?: boolean;
    /** 标题 */
    title?: string;
    /** 加载 */
    loading?: boolean;
    /** 配置 */
    config?: {
        title: string; // data里面对应的title的key
        key: string; // data里面对应的key的key
        num?: string | number; // data里面对应的num的key
    };
}

const textType = {
    add: "添加",
    edit: "编辑",
};

const props = defineProps<Props>();
const emit = defineEmits(["add", "delete", "edit"]);
const {data = [], width = 230, enableAdd = false, title = "分组", config, loading = false} = props;
console.log("props", toRaw(props));

const {SchemaField} = createSchemaField({
    components: {FormItem, Input},
});

const form = createForm();
const open = ref(false);
const type = ref<"add" | "edit">("add");
const list = reactive(data);

const schema = {
    type: "object",
    properties: {
        title: {
            type: "string",
            "x-decorator": "FormItem",
            "x-component": "Input", // createSchemaField 对应components里面的组件
            required: true,
            "x-component-props": {
                placeholder: "请输入内容， 100 个字符以内",
                maxlength: 10,
                showCount: true,
            },
        },
        edit: {
            type: "string",
            "x-hidden": true,
            "x-decorator": "FormItem",
            "x-component": "Input",
            default: "",
        },
    },
};
// 弹窗 打开
const handleOpen = () => {
    form.reset();
    type.value = "add";
    open.value = true;
};

// 编辑
const handleEdit = row => {
    const info = {title: row[config.title], edit: row};
    form.setValues(info);
    type.value = "edit";
    open.value = true;
};

// 删除
const handleDelete = row => {
    Modal.warning({
        title: "确定删除分组",
        cancelText: "取消",
        okText: "确定",
        onOk: () => {
            emit("delete", row);
        },
    });
};

// 确定
const handleOk = () => {
    form.submit(value => {
        console.log("value", type.value, value);
        if (type.value === "edit") {
            const info = {...value.edit, [config.title]: value.title};
            emit("edit", info);
        } else {
            emit("add", value.title);
        }
        open.value = false;
    });
};
</script>

<style scoped lang="less">
.grouping {
    width: 230px;
    height: 100%;
    display: flex;
    flex-direction: column;
    background: #fff;

    .header {
        padding: 0 12px 0 20px;
        border-bottom: 1px solid #e9e9e9;
        &-title {
            justify-content: space-between;
            min-height: 56px;
            div {
                font-size: 14px;
                font-weight: 600;
                color: rgba(0, 0, 0, 0.85);
            }
        }
    }
    .list {
        width: 100%;
        box-sizing: border-box;
        height: 100%;
        overflow-y: scroll;
        padding: 12px;
        .item {
            justify-content: space-between;
            padding: 7px 12px;
            background: #fff;
            border-radius: 2px;
            cursor: pointer;
            padding: 8px !important;
            margin-bottom: 8px;
            border-radius: 4px;
            &-left {
                .icon {
                    margin-right: 6px;
                }
            }
        }
    }
}
</style>
